package com.ermax.aircond.report.dao;

import java.io.Serializable;
import java.util.Date;
import java.util.List;

import javax.annotation.Resource;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.envers.AuditReader;
import org.hibernate.envers.AuditReaderFactory;
import org.hibernate.envers.query.AuditEntity;
import org.hibernate.envers.query.AuditQuery;
import org.springframework.stereotype.Repository;

@Repository("auditLogDao")
public class AuditLogDao implements java.io.Serializable {

	/**
	 * 
	 */
	private static final long serialVersionUID = 1L;
	@Resource(name = "sessionFactory")
	private SessionFactory sessionFactory;

	@SuppressWarnings("unchecked")
	public <T> T getDomainByVersion(Class<?> clazz, final Serializable primaryKey, final int versionId) {
		AuditReader auditReader = AuditReaderFactory.get(getCurrentSession());
		return (T) auditReader.find(clazz, primaryKey, versionId);
	}

	public List<Number> getRevNumbers(Class<?> clazz, final Serializable primaryKey) {
		AuditReader auditReader = AuditReaderFactory.get(getCurrentSession());
		return auditReader.getRevisions(clazz, primaryKey);
	}

	@SuppressWarnings("unchecked")
	public List<Object> getRevEntities(Class<?> clazz, Object entityId, Date fromDate, Date toDate, String auditedByUserName){
		AuditReader auditReader = AuditReaderFactory.get(getCurrentSession());
		AuditQuery query = auditReader.createQuery().forRevisionsOfEntity(clazz, false, true);
		
		if(entityId != null){
			query.add(AuditEntity.id().eq(entityId));
		}
		
		if (fromDate != null) {
			query.add(AuditEntity.revisionProperty("timestamp").ge(fromDate.getTime()));
		}

		if (toDate != null) {
			query.add(AuditEntity.revisionProperty("timestamp").le(toDate.getTime()));
		}

		if (auditedByUserName != null) {
			query.add(AuditEntity.revisionProperty("username").eq(auditedByUserName));
		}

		Object obj = query.getResultList();
		
		return (List<Object>) obj;
	}
	

	public List<Object> getRevEntities(Class<?> clazz, Date fromDate, Date toDate, String auditedByUserName) {

		return getRevEntities(clazz,null,fromDate,toDate,auditedByUserName);

	}

	protected Session getCurrentSession() {
		return this.sessionFactory.getCurrentSession();
	}
}
